import type { TweenEasing } from 'cc';
import { _decorator, Component, instantiate, Prefab, ProgressBar, resources, Tween, tween, UIOpacity, v3 } from 'cc';
import { Ab_DataTransfer_bA } from '../../../A-FRAME/A-LIB/lib.b.data';
import { Ab_ClientAPI_bA } from '../../api/client.api';
import { Ab_AudioManager_bA } from '../../manager/audio-manager';
import Ab_GameDC_bA from '../../manager/data.game.center';
import Ab_GameManager_bA from '../../manager/game.manager';
const { ccclass, property } = _decorator;

@ccclass('Ab_Loading_bA')
export class Ab_Loading_bA extends Component {

	@property(ProgressBar)
	private bar: ProgressBar = null;

	private prmz_init: Promise<void>;

	private progress_ctrl: ProgressCtrl;

	protected onLoad(){
		this.progress_ctrl = new ProgressCtrl(11, 5, 0.3);
		this.progress_ctrl.onProgressChange((progress, current, total)=>this.Ab_updateProgress_bA(progress, current, total));
		this.progress_ctrl.DONE.then(()=>this.Ab_enterGame_bA());
	}

    start() {
		this.Ab_GameInit_bA();
		this.Ab_loadGame_bA();
		this.Ab_adaptUI_bA();
    }

	private Ab_updateProgress_bA(progress: number, current: number, total: number){
		this.bar.progress = progress;
	}

	private Ab_adaptUI_bA(){
		this.bar.progress = 0;
		abi.Ab_cc_bA.Ab_adaptBackgroundNode_bA(this.node.getChildByName('background'));
	}

	private Ab_GameInit_bA(){
		this.prmz_init = Ab_ClientAPI_bA.Ab_Local_bA().then(res=>Ab_GameManager_bA.Ab_init_bA(res.Ab_countryCode_bA));
	}

	private Ab_loadGame_bA(){
		let count = 0;
		['home-bg', 'game', 'home-ui', 'transition', 'pop-up', 'float', 'guide'].forEach((name, index)=>resources.load(
			'prefab/page/'+name, Prefab,
			(err, prefab)=>{
				count++;
				let node = instantiate(prefab);
				node.active = false;
				node.setParent(this.node.parent);
				this.progress_ctrl.completeOne();
				if(count==7){
					this.Ab_loadDone_bA();
				}
			})
		);
	}

	private Ab_loadDone_bA(){
		['Camera', 'audio', 'home-bg', 'game', 'home-ui', 'transition', 'pop-up', 'float', 'guide', 'loading']
		.forEach((name, index)=>this.node.parent.getChildByName(name).setSiblingIndex(index));

		this.prmz_init.then(()=>{
			this.node.parent.children.forEach(node=>node.name=='Camera' ? void 0 : node.active = true);
			this.Ab_otherPreprocess_bA().then(()=>this.progress_ctrl.completeOne());
		});
	}

	private Ab_otherPreprocess_bA(){
		Ab_ClientAPI_bA.Ab_CloseLoading_bA();
		let np_pltp = new abi.Ab_NudityPromise_bA<'end'>();
		let reg_pltp = Ab_DataTransfer_bA.Ab_follow_bA(Ab_GameDC_bA.Ab_Trigger_bA, 'Ab_PreLoadTilesProgress_bA', ()=>{
			let [t, f] = Ab_GameDC_bA.Ab_Trigger_bA.Ab_PreLoadTilesProgress_bA.split(',').map(Number);
			if(t===f){
				Ab_DataTransfer_bA.Ab_cancel_bA(reg_pltp);
				np_pltp.Ab_resolve_bA('end');
				this.progress_ctrl.completeOne();
			}
		}, false);
		Ab_GameDC_bA.Ab_Trigger_bA.Ab_PreLoadTiles_bA = true;

		let np_lcp = new abi.Ab_NudityPromise_bA<'end'>();
		let reg_lcp = Ab_DataTransfer_bA.Ab_follow_bA(Ab_GameDC_bA.Ab_Trigger_bA, 'Ab_LiveCommentsProgress_bA', ()=>{
			let [f, t] = Ab_GameDC_bA.Ab_Trigger_bA.Ab_LiveCommentsProgress_bA.split(',').map(Number);
			if(t===f){
				Ab_DataTransfer_bA.Ab_cancel_bA(reg_lcp);
				np_lcp.Ab_resolve_bA('end');
				this.progress_ctrl.completeOne();
			}
		}, false);

		let np_guide = new abi.Ab_NudityPromise_bA<'end'>();
		if(Ab_GameDC_bA.Ab_Status_bA.Ab_guideInited_bA){
			np_guide.Ab_resolve_bA('end');
		}else{
			let reg = Ab_DataTransfer_bA.Ab_follow_bA(Ab_GameDC_bA.Ab_Status_bA, 'Ab_guideInited_bA', (_, inited)=>{
				Ab_DataTransfer_bA.Ab_cancel_bA(reg);
				np_guide.Ab_resolve_bA('end');
			}, false);
		}

		np_guide.Ab_promise_bA.then(()=>this.progress_ctrl.completeOne());

		return Promise.all([np_pltp.Ab_promise_bA, np_lcp.Ab_promise_bA, np_guide.Ab_promise_bA]);
	}


	private Ab_enterGame_bA(){
		let [bg, logo, bar] = ['background', 'logo', 'progress-bar'].map(name=>this.node.getChildByName(name));

		let [va_logo, va_bar] = [logo, bar].map(n=>new abi.Ab_cc_bA.Ab_VecAssist_bA(n));
		va_logo.Ab_getPosition_bA('Ab_center_bA', 'Ab_over_top_bA').x = logo.position.x;
		va_bar.Ab_getPosition_bA('Ab_center_bA', 'Ab_over_bottom_bA').x = bar.position.x;

		let duration = 0.8;
		const easing: TweenEasing = 'cubicOut';
		tween(logo).to(duration, {position: va_logo.Ab_vec_bA}, {easing}).start();
		tween(bar).to(duration, {position: va_bar.Ab_vec_bA}, {easing}).start();

		//let [bg, bar] = ['background', 'progress-bar'].map(name=>this.node.getChildByName(name));

		//let va_bar = new abi.Ab_cc_bA.Ab_VecAssist_bA(bar);
		//va_bar.Ab_getPosition_bA('Ab_center_bA', 'Ab_over_bottom_bA').x = bar.position.x;

		//let duration = 0.8;
		//const easing: TweenEasing = 'cubicOut';
		//tween(bar).to(duration, {position: va_bar.Ab_vec_bA}, {easing}).start();

		let opt = bg.getComponent(UIOpacity);
		if(!opt) opt = bg.addComponent(UIOpacity);

		tween(opt).to(duration, {opacity: 0}, {easing}).start();
		tween(bg).to(duration, {scale: v3(1.5, 1.5, 1)}, {easing})
		.call(()=>{
			this.node.destroy();
			Ab_AudioManager_bA.Ab_playBGM_bA();
		}).start();

		Ab_GameDC_bA.Ab_Trigger_bA.Ab_LoadRound_bA = Ab_GameDC_bA.Ab_User_bA.Ab_round_bA;
		//Ab_GameDC_bA.Ab_Trigger_bA.Ab_LoadRound_bA = 4;
		Ab_GameDC_bA.Ab_Trigger_bA.Ab_UIHome_bA = true;
		Ab_GameDC_bA.Ab_Trigger_bA.Ab_UIGame_bA = true;
		Ab_AudioManager_bA.Ab_mute_bA(!Ab_GameDC_bA.Ab_User_bA.Ab_bgm_bA);
	}
}

class ProgressCtrl {
	private done: number;
	private __progress__: number;
	private set progress(progress: number){
		this.__progress__ = progress;
		if(this.on_progress_change_call_list.length>0){
			this.on_progress_change_call_list.forEach(call=>{
				try{
					call(progress, this.done, this.total);
				}catch(err){
					console.warn('[Error]: ProgressCtrl@<file:loading.ts:175>', err);
				}
			});
		}
	}
	public get progress(){
		return this.__progress__;
	}
	private np: abi.Ab_NudityPromise_bA<'end'>;

	public get DONE(){
		return this.np.Ab_promise_bA;
	}

	constructor(private total: number, private normal_duration: number, private done_duration: number){
		this.np = new abi.Ab_NudityPromise_bA();
		this.done = 0;
		this.progress = 0;
	};

	public completeOne(){
		this.done = Math.min(this.total, this.done+1);
		this.updateProgress();
	}

	private updateProgress(){
		let progress = Math.min(1, this.done / this.total);
		if(progress==this.progress){
			return void 0;
		}
		Tween.stopAllByTarget(this);

		let done = progress>=1;
		let tw = tween<ProgressCtrl>(this);
		if(done){
			tw = tw.to(this.done_duration, {progress})
			.delay(0.3)
			.call(()=>this.np.Ab_resolve_bA('end'));
		}else{
			tw = tw.to(this.normal_duration, {progress});
		}

		tw.start();
	}

	private on_progress_change_call_list: Array<(progress: number, current: number, total: number)=>void> = [];
	public onProgressChange(call: (progress: number, current: number, total: number)=>void){
		this.on_progress_change_call_list.push(call);
	}
}
